/*
* Copyright 2011 Pavel Kozhin 
*
* Licensed under the Apache License, Version 2.0 (the "License"); 
* you may not use this file except in compliance with the License. 
* You may obtain a copy of the License at 
* 
* http://www.apache.org/licenses/LICENSE-2.0
* 
* Unless required by applicable law or agreed to in writing, software 
* distributed  under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
* See the License for the specific language governing permissions and 
* limitations under the License.
*
* Author: Pavel Kozhin.
*/
package org.etherframework.core.bridge
{
	import flash.errors.IllegalOperationError;
	import flash.events.Event;
	
	import org.etherframework.IEther;
	import org.etherframework.core.context.Context;
	import org.etherframework.core.events.InteractionEvent;
	import org.etherframework.core.utils.Dispatcher;

	[ExcludeClass]
	public class BridgeInteraction implements IInteraction
	{
		private static var _context:Context;
		
		private var _bridge:IBridge;
		private var _dispatcher:Dispatcher;
		private var _initialized:Boolean = false;
		
		public function initialize(bridge:IBridge, dispatcher:Dispatcher):void
		{
			if (_initialized)
				throw new IllegalOperationError("IBridgeInteraction is already initialized.");
			if (!bridge)
				throw new ArgumentError("Argument bridge:IBridge can not be null.");
			if (!dispatcher)
				throw new ArgumentError("Argument dispatcher:Dispatcher can not be null.");
			
			_bridge = bridge;
			_dispatcher = dispatcher;
			_initialized = true;
		}
		
		public function dispatchEvent(owner:IEther, event:Event):void
		{
			if (!event)
				throw new ArgumentError("Argument event:Event can not be null.");
			
			const context:Context = _context || owner.context;
			
			_dispatcher.source.dispatchEvent(
				new InteractionEvent(event.type + context, _bridge, event));
		}
		
		public function listenEvent(owner:IEther, type:String, listener:Function):void
		{
			_dispatcher.listen(owner, type + owner.context, listener, false, 0, true);
		}
		
		public function unlistenEvent(owner:IEther, type:String, listener:Function):void
		{
			_dispatcher.unlisten(owner, type + owner.context, listener);
		}
		
		public function unlistenAll(owner:IEther):void
		{
			_dispatcher.unlistenAll(owner);
		}
		
		public function retainContext(owner:IEther):void
		{
			_context = owner.context;
		}
		
		public function releaseContext():void
		{
			_context = null;
		}
	}
}